package com.atguigu.gulimall.product;

import com.alibaba.alicloud.context.oss.OssContextAutoConfiguration;
import com.alibaba.cloud.seata.GlobalTransactionAutoConfiguration;
import org.mybatis.spring.annotation.MapperScan;
import org.redisson.spring.session.config.EnableRedissonHttpSession;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.cache.annotation.EnableCaching;
import org.springframework.cloud.client.discovery.EnableDiscoveryClient;
import org.springframework.cloud.openfeign.EnableFeignClients;
import org.springframework.session.data.redis.config.annotation.web.http.EnableRedisHttpSession;

/**
 * 1.整合mybatis-plus
 * 1)、导入依赖
         <dependency>
         <groupId>com.baomidou</groupId>
         <artifactId>mybatis-plus-boot-starter</artifactId>
         <version>3.2.0</version>
         </dependency>

 2)、配置
    1、配置数据源:
        1、配置数据源:
           1)、导入数据库的驱动.
           2)、在application.yml 配置数据源相关的信息
        2、配置Mybatis-Plus:
            1)、使用@MapperScan
            2)、告诉Mybatis-Plus，sql映射文件位置
2.逻辑删除
    1).配置全局的逻辑删除规则(可省略)
    2).配置逻辑删除的组件Bean(可省略)
    3).给Bean加上逻辑删除注解@TableLogic

 3、JSR303
    1)、给Bean添加校验注解:javax.validation.constraints
    2)、开启校验功能@Valid
        效果：检验错误以后会有默认的响应:
    3)、给校验的bean后紧跟一个BingingResult，就可以获得校验的结果

    4)、分组校验(多场景的复杂校验)
        1)、@NotBlank(message = "品牌名必须提交",groups = {AddGroup.class,UpdateGroup.class})
         给校验注解标注什么情况需要进行校验
        2)、@Validated({Addgroup.class})
        3)、默认没有指定分组的校验注解@NotBlank，在分组的校验情况@Validated({Addgroup.class})下不生效
    5)、自定义校验
        1)、编写一个自定义的校验注解
        2)、编写一个自定义的校验器
        3)、关联自定义的校验器和自定义的校验注解
         @Documented
         @Constraint(
         validatedBy = { ListValueConstraintValidator.class,xxx.class}
         )
            //可以指定多个不同的校验器 适配不同的类型的校验
         @Target({ElementType.METHOD, ElementType.FIELD, ElementType.ANNOTATION_TYPE, ElementType.CONSTRUCTOR, ElementType.PARAMETER, ElementType.TYPE_USE})
         @Retention(RetentionPolicy.RUNTIME)
 public @interface ListValue {
 4、统一的异常处理类
 @ControllerAdvice
 1)、编写异常处理类,使用@ControllerAdvice。
 2）、使用@ExceptionHandler标注方法可以处理的异常
 5、模板引擎
    1)、thymeleaf-starter 关闭缓存
    2)、静态资源都放在static文件下就可以按照路径直接访问
    3)、页面放在template下,直接访问
        springboot,访问项目的时候,会默认找index
    4)、页面修改不会重启服务器实时更新
        1)、引入dev-tools
        2)、修改页面 ctrl  + shift + f9 重新启动编译一下 (如果是代码配置还是重启一下配置)
 6、整合redis
    1）、引入data-redis-starter
    2）、简单配置redis的host的信息
    3）、使用SpringBoot自动配置好的StringRedisTemplate来操作redis

    redis->map ：  存放数据key，数据值value
 7、 整合redisson
    1)、引入依赖
     <dependency>
     <groupId>org.redisson</groupId>
     <artifactId>redisson</artifactId>
     <version>3.12.0</version>
     </dependency>
    2）、配置redisson

 8.整合SpringCache 简化缓存开发
    1)、引入依赖
        spring-boot-starter-cache、 spring-boot-starter-data-redis
    2)、写配置
        （1）.自动配置了哪些
            CacheAuroConfiguration 会导入RedisCacheConfiguration;
        自动配置好了缓存管理器RedisCacheManager
        (2)、配置使用redis作为缓存
        (3)、测试使用缓存
            @Cacheable 触发将数据保存到胡残存的操作
            @CacheEvict: 触发将数据从缓存删除的操作
            @CachePut: 不影响方法执行更新缓存
            @Caching:组合以上多个操作
            @CacheConfig: 在类级别共享缓存的相同配置
        1)、开启缓存功能@EnableCacheing
        2)、只需要使用注解就能完成缓存操作
    4)、原理:
    CacheAutoConfiguration -> RedisCacheConfiguration ->
    自动配置了RedisCacheManager->初始化所有的缓存->每一个缓存决定使用什么配置->
    如果reidsCacheConfiguration有就用已有的,没有就使用默认配置
    ->想改缓存的配置,只需要给容器中放一个RedisCacheConfiguration即可
    ->就会应用到当前RedisCacheManager 管理的所有的缓存分区中
 */

@EnableRedisHttpSession
@EnableCaching
@EnableFeignClients(basePackages = "com.atguigu.gulimall.product.feign")
@MapperScan("com.atguigu.gulimall.product.dao")
@EnableDiscoveryClient
@SpringBootApplication(exclude = {OssContextAutoConfiguration.class, GlobalTransactionAutoConfiguration.class})
public class GulimallProductApplication {

    public static void main(String[] args) {
        SpringApplication.run(GulimallProductApplication.class, args);
    }

}
